import React, { useEffect, useState } from 'react';
import { dynamic } from 'umi';
import style from './style.module.less';
import { FileImageOutlined } from '@ant-design/icons';
import { useDebounceFn, useMount, useUpdateEffect } from 'ahooks';
import ImageUploadDialog from '../ImageUploadDialog';

export interface EditorProps {
  value?: string;
  height?: number;
  defaultValue?: string;
  onChange?: (html: string) => void;
}

// 图片上传态
const useImageUploadState = (params: {
  onSuccess: (images: string[]) => void;
}) => {
  const [visible, setVisible] = useState<boolean>(false);

  return {
    visible,
    open: () => {
      setVisible(true);
    },
    close: () => setVisible(false),
    onSuccess: params.onSuccess,
  };
};

export default dynamic({
  loader: async () => {
    const { default: BraftEditor } = await import(
      /* webpackChunkName: "braft" */ 'braft-editor'
    );
    const { ContentUtils } = await import(
      /* webpackChunkName: "braft" */ 'braft-utils'
    );
    await import(/* webpackChunkName: "braft" */ 'braft-editor/dist/index.css');

    return (props: EditorProps) => {
      const [editor, setEditor] = useState(
        BraftEditor.createEditorState(props.value ?? props.defaultValue),
      );

      // 节流输入
      const { run: inputDebounce } = useDebounceFn(
        val => {
          if (val === '' || val === '<p></p>') {
            props.onChange && props.onChange('');
          } else {
            props.onChange && props.onChange(val);
          }
        },
        { wait: 500 },
      );
      useEffect(() => {
        const yValue = editor.toHTML();
        const nValue = BraftEditor.createEditorState(
          props.value ?? props.defaultValue,
        );

        if (yValue != nValue.toHTML()) {
          setEditor(nValue);
        }
      });
      useUpdateEffect(() => {
        const yValue = editor.toHTML();
        const nValue = BraftEditor.createEditorState(
          props.value ?? props.defaultValue,
        );

        if (yValue != nValue.toHTML()) {
          setEditor(nValue);
        }
      }, [props.value]);

      const image = useImageUploadState({
        onSuccess: (images: string[]) => {
          setEditor(
            ContentUtils.insertMedias(
              editor,
              images.map(image => {
                return {
                  type: 'IMAGE',
                  url: image,
                };
              }),
            ),
          );
        },
      });

      const controls: any[] = [
        'undo',
        'redo',
        'separator',
        'headings',
        'font-size',
        'line-height',
        'letter-spacing',
        'separator',
        'text-color',
        'bold',
        'italic',
        'underline',
        'strike-through',
        'separator',
        'superscript',
        'subscript',
        'remove-styles',
        'separator',
        'text-indent',
        'text-align',
        'separator',
        'list-ul',
        'list-ol',
        'blockquote',
        'code',
        'separator',
        'link',
        'hr',
        {
          key: 'image',
          type: 'button',
          title: '插入图片',
          text: <FileImageOutlined />, // 指定按钮文字，此处可传入jsx，若已指定html，则text不会显示
          onClick: () => {
            image.open();
            console.log('click');
          },
        },
        'separator',
        'clear',
      ];

      return (
        <div className={style.editor}>
          <ImageUploadDialog
            multiple={true}
            onOk={(images: string[]) => {
              image.close();

              image.onSuccess(
                images.map(image => {
                  return image;
                }),
              );
            }}
            onCancel={() => image.close()}
            visible={image.visible}
          />

          <BraftEditor
            value={editor}
            controls={controls}
            // onChange={state => {
            //   setEditor(state);
            //   const html = state.toHTML();
            //   if (props.onChange && props.value != html) {
            //     inputDebounce(html);
            //     // props.onChange(state.toHTML());
            //   }
            // }}
          />
        </div>
      );
    };
  },
});
